package local

import (
	"fmt"
	"strconv"

	"gorm.io/gorm"
)

/* --- Form 结构示例

type TestData struct {
	ID           utils.LocalStr         `forms:"id"` (TODO &str="N2" 可正常接受, &str=N2 不能正常接受)
	Status       utils.LocalInt         `forms:"status"`
	DateGte      utils.LocalDate        `forms:"dateGte"`
	Page         int                    `forms:"current"`
	Size         int                    `forms:"pageSize"`
	Sorter       map[string]interface{} `forms:"sorter"`
	Filter       map[string]interface{} `forms:"filter"`
}

// 接受数据
var forms format.TestData
err := c.ShouldBindQuery(&forms)

// 数据库筛选数据
func TestList(forms *format.TestData) (int64, []model.Test) {
	offset := (forms.Page - 1) * forms.Size
	var count int64
	var items []model.Test
	query := utils.Db.Model(&model.Test{}).Where("branchcode = ?", branchCode)
	utils.FilterStr(query, "id", forms.ID)
	utils.FilterInt(query, "status", forms.Status)
	utils.FilterLocalDate(query, "date", forms.DateGte, utils.LocalDate{})
	utils.Filter(query, forms.Filter)
	utils.Sorter(query, forms.Sorter)
	err := query.Order("id desc").Count(&count).Limit(forms.Size).Offset(offset).Find(&items).Error
	if err == nil {
		return count, items
	}
	return 0, nil
}

--- */

// Sorter 把 sorter:{"type":"ascend", "status":"descend"} 排序加到查询语句中
func Sorter(query *gorm.DB, sorter map[string]interface{}) {
	if sorter != nil {
		for key, value := range sorter {
			order := fmt.Sprintf("`%s`", key)
			if value == "descend" {
				order = fmt.Sprintf("`%s` desc", key)
			}
			query = query.Order(order)
		}
	}
}

// Filter 把 filter:{"type":[1, 2]} 多选筛选加到查询语句中
func Filter(query *gorm.DB, filter map[string]interface{}) {
	if filter != nil {
		for key, value := range filter {
			query = query.Where(fmt.Sprintf("`%s` IN ?", key), value)
		}
	}
}

// FilterJoinInt 过滤 0 值 int
func FilterJoinInt(query *gorm.DB, column string, value int) {
	if value != 0 {
		query.Where(fmt.Sprintf("%s = ?", column), value)
	}
}

// FilterInt 过滤 0 值 int
func FilterInt(query *gorm.DB, column string, value int) {
	if value != 0 {
		query.Where(fmt.Sprintf("`%s` = ?", column), value)
	}
}

// FilterInt64 过滤 0
func FilterInt64(query *gorm.DB, column string, value int64) {
	if value != 0 {
		query.Where(fmt.Sprintf("`%s` = ?", column), value)
	}
}

// FilterJoinStr 过滤字符串
func FilterJoinStr(query *gorm.DB, column string, value string) {
	if value != "" {
		query.Where(fmt.Sprintf("%s = ?", column), value)
	}
}

// FilterStr 过滤字符串
func FilterStr(query *gorm.DB, column string, value string) {
	if value != "" {
		query.Where(fmt.Sprintf("`%s` = ?", column), value)
	}
}

// LikeType like 语句类型, 前加 %、后加 %、都加 %
type LikeType int

const (
	AheadLike LikeType = 1
	LaterLike LikeType = 2
	BothLike  LikeType = 3
)

// FilterLikeInt 匹配 like 语句。剔除 0 值
func FilterLikeInt(query *gorm.DB, column string, num int, likeType LikeType) {
	if num != 0 {
		value := strconv.Itoa(num)
		FilterLikeStr(query, column, value, likeType)
	}
}

// FilterLikeStr 匹配 like 语句。剔除空字符串。
func FilterLikeStr(query *gorm.DB, column string, value string, likeType LikeType) {
	if value != "" {
		switch likeType {
		case AheadLike:
			query.Where(fmt.Sprintf("`%s` like '%s' ", column, "%"+value))
		case LaterLike:
			query.Where(fmt.Sprintf("`%s` like '%s' ", column, value+"%"))
		case BothLike:
			query.Where(fmt.Sprintf("`%s` like '%s' ", column, "%"+value+"%"))
		}
	}
}

// FilterLikeStrArr 匹配 like 数组，用 or 连接。
func FilterLikeStrArr(query *gorm.DB, column string, values []string) {
	sqlStr := ""
	for _, value := range values {
		if value == "" {
			continue
		}
		if sqlStr == "" {
			sqlStr = fmt.Sprintf("`%s` like '%s' ", column, "%"+value+"%")
		} else {
			sqlStr = sqlStr + fmt.Sprintf(" or `%s` like '%s' ", column, "%"+value+"%")
		}
	}
	query.Where(sqlStr) // fmt.Sprintf("(%s)"), gorm 回给每一个 where 都会 加 ()
}

/* ------ 自定义类型过滤 ------ */

// FilterLocalStr 过滤字符串
func FilterLocalStr(query *gorm.DB, column string, value LocalStr) {
	if value.NotNil() {
		query.Where(fmt.Sprintf("`%s` = ?", column), value)
	}
}

// FilterLocalInt 过滤字 int
func FilterLocalInt(query *gorm.DB, column string, value LocalInt) {
	if value.Int != nil {
		query.Where(fmt.Sprintf("`%s` = ?", column), value.Int)
	}
}

// FilterLocalDate 忽略默认时间 (greater than or equal, less than or equal)
func FilterLocalDate(query *gorm.DB, column string, gte LocalDate, lte LocalDate) {
	if gteValue, _ := gte.Value(); gteValue != nil {
		query.Where(fmt.Sprintf("`%s` >= ?", column), gteValue)
	}
	if lteValue, _ := lte.Value(); lteValue != nil {
		query.Where(fmt.Sprintf("`%s` <= ?", column), lteValue)
	}
}

// FilterLocalDatetime 忽略默认时间
func FilterLocalDatetime(query *gorm.DB, column string, gte LocalDatetime, lte LocalDatetime) {
	if gteValue, _ := gte.Value(); gteValue != nil {
		query.Where(fmt.Sprintf("`%s` >= ?", column), gteValue)
	}
	if lteValue, _ := lte.Value(); lteValue != nil {
		query.Where(fmt.Sprintf("`%s` <= ?", column), lteValue)
	}
}

func FilterInData(query *gorm.DB, column string, data interface{}) {
	if data, ok := data.([]int); ok {
		query.Where(column+" in ?", data)
	}

	if data, ok := data.([]int64); ok {
		query.Where(column+" in ?", data)
	}

	if data, ok := data.([]string); ok {
		query.Where(column+" in ?", data)
	}
}
